package com.difsonapps.contacttranslator.utils;

import java.io.BufferedWriter;
import java.io.File;
import java.io.FileWriter;
import java.io.IOException;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;

import javax.xml.parsers.DocumentBuilder;
import javax.xml.parsers.DocumentBuilderFactory;

import org.hibernate.SessionFactory;
import org.jdom2.Document;
import org.jdom2.Element;
import org.jdom2.Namespace;
import org.jdom2.input.SAXBuilder;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Repository;
import org.springframework.transaction.annotation.Transactional;



public class DAOGenerator {

	Document doc;
	Namespace ns;

	
	public DAOGenerator(Document doc,Namespace ns) {
		this.doc = doc;
		this.ns=ns;
		// TODO Auto-generated constructor stub
	}

	public String initGenerate(Element complexTypeElement) {
        String complexTypeName = complexTypeElement.getAttributeValue("name");
        
        System.out.println("complexTypeName : "+complexTypeName);
       
        String dTOClassName=UtilGenerator.firstToUpper(complexTypeName);
        String dTOVarName=UtilGenerator.firstToLower(complexTypeName);
        
		StringBuilder strBuilder = new StringBuilder();
		strBuilder.append("package com.diffogroup.contacttranslator.dao;\n");
		strBuilder.append("import org.hibernate.SessionFactory;\n");
		strBuilder.append("import java.util.*;\n");
		strBuilder.append("import org.springframework.beans.factory.annotation.Autowired;\n");
		strBuilder.append("import org.springframework.stereotype.Repository;\n");
		strBuilder.append("import org.springframework.transaction.annotation.Transactional;\n");
		strBuilder.append("import com.diffogroup.contacttranslator.dto."+dTOClassName+";\n");
		
		strBuilder.append("@Repository\n");
		strBuilder.append("@Transactional\n");
		
		strBuilder.append("public class "+UtilGenerator.dtoToDAO(dTOClassName)+" {\n"); 
		strBuilder.append("@Autowired\n");
		strBuilder.append("protected SessionFactory sessionFactory;\n");
		
		return strBuilder.toString();
	}


	public String insertGenerate(Element complexTypeElement) {
        String complexTypeName = complexTypeElement.getAttributeValue("name");
        
        System.out.println("complexTypeName : "+complexTypeName);
       
        String dTOClassName=UtilGenerator.firstToUpper(complexTypeName);
        String dTOVarName=UtilGenerator.firstToLower(complexTypeName);
        
		StringBuilder strBuilder = new StringBuilder();
		strBuilder.append("@Transactional\n");
		strBuilder.append("public void insert("+dTOClassName+" "+dTOVarName+"){\n"); 
		strBuilder.append("sessionFactory.getCurrentSession().save("+dTOVarName+");\n");
		strBuilder.append("}\n");
		return strBuilder.toString();
	}

	
	public String updateGenerate(Element complexTypeElement) {
		  String complexTypeName = complexTypeElement.getAttributeValue("name");
	        
	        System.out.println("complexTypeName : "+complexTypeName);
	       
	        String dTOClassName=UtilGenerator.firstToUpper(complexTypeName);
	        String dTOVarName=UtilGenerator.firstToLower(complexTypeName);
	        
			StringBuilder strBuilder = new StringBuilder();
			strBuilder.append("@Transactional\n");
			strBuilder.append("public void update("+dTOClassName+" "+dTOVarName+"){\n"); 
			strBuilder.append("sessionFactory.getCurrentSession().update("+dTOVarName+");\n");
			strBuilder.append("}\n");
			return strBuilder.toString();
	}
	
	public String getGenerate(Element complexTypeElement) {
		  String complexTypeName = complexTypeElement.getAttributeValue("name");
	        
	        System.out.println("complexTypeName : "+complexTypeName);
	       
	        String dTOClassName=UtilGenerator.firstToUpper(complexTypeName);
	        String dTOVarName=UtilGenerator.firstToLower(complexTypeName);
	        
			StringBuilder strBuilder = new StringBuilder();
			strBuilder.append("@Transactional\n");
			strBuilder.append("public "+dTOClassName+" get(int id) {"); 
			strBuilder.append("return ("+dTOClassName+") sessionFactory.getCurrentSession().get("+dTOClassName+".class,id);\n");
			strBuilder.append("}\n");
			return strBuilder.toString();
	}
	
	public String getAllGenerate(Element complexTypeElement) {
		  String complexTypeName = complexTypeElement.getAttributeValue("name");
	        System.out.println("complexTypeName : "+complexTypeName);
	        String dTOClassName=UtilGenerator.firstToUpper(complexTypeName);
	        String dTOVarName=UtilGenerator.firstToLower(complexTypeName);	        
			StringBuilder strBuilder = new StringBuilder();
			strBuilder.append("@SuppressWarnings(\"unchecked\")\n");
			strBuilder.append("@Transactional\n");
			strBuilder.append("public List<"+dTOClassName+"> getAll() {"); 
			strBuilder.append("return (List<"+dTOClassName+">) sessionFactory.getCurrentSession().createQuery(\"Select t from "+dTOClassName+" t\").list();\n");
			strBuilder.append("}\n");
			return strBuilder.toString();
	}

	public String deleteGenerate(Element complexTypeElement) {
        String complexTypeName = complexTypeElement.getAttributeValue("name");
        
        System.out.println("complexTypeName : "+complexTypeName);
       
        String dTOClassName=UtilGenerator.firstToUpper(complexTypeName);
        String dTOVarName=UtilGenerator.firstToLower(complexTypeName);
        
		StringBuilder strBuilder = new StringBuilder();
		strBuilder.append("@Transactional\n");
		strBuilder.append("public void delete("+dTOClassName+" "+dTOVarName+"){\n"); 
		strBuilder.append("sessionFactory.getCurrentSession().delete("+dTOVarName+");\n");
		strBuilder.append("}\n");
		return strBuilder.toString();
	}
	
	public String endGenerate(Element complexTypeElement) {    
		StringBuilder strBuilder = new StringBuilder();
		strBuilder.append("}\n");
		return strBuilder.toString();
	}
	
	
	public void daoConstuct(Element complexTypeElement) {  
		  String complexTypeName = complexTypeElement.getAttributeValue("name");
	        
	        System.out.println("complexTypeName : "+complexTypeName);
	       
	        String dTOClassName=UtilGenerator.firstToUpper(complexTypeName);
	        String dTOVarName=UtilGenerator.firstToLower(complexTypeName);
	        
		StringBuilder strBuilder = new StringBuilder();
		strBuilder.append(initGenerate(complexTypeElement));
		strBuilder.append(insertGenerate(complexTypeElement));
		strBuilder.append(updateGenerate(complexTypeElement));
		strBuilder.append(getGenerate(complexTypeElement));
		strBuilder.append(getAllGenerate(complexTypeElement));
		strBuilder.append(deleteGenerate(complexTypeElement));
		strBuilder.append(endGenerate(complexTypeElement));
		
		File file = new File(UtilGenerator.dAOPath(dTOClassName));
		FileWriter fw;
		BufferedWriter bw;
		try {
			fw = new FileWriter(file.getAbsoluteFile());
			 bw= new BufferedWriter(fw);
			bw.write(strBuilder.toString());
			bw.close();
		} catch (IOException e) {
			e.printStackTrace();
		}
		
	}
	
	
	public void generate() {
		Element rootNode = doc.getRootElement();
		System.out.println("rootNode "+rootNode.getName());
		List<Element> list = rootNode.getChildren("complexType",ns);
		for(Element element:list)
		{
			  String name = element.getAttributeValue("name");
			  if(UtilGenerator.containt(name, "DTO"))
			  {
			   daoConstuct(element);
			  }
		}
		
	}
	
	
	
}
